package com.hxkj.service.impl;


import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.TypeReference;
import com.hxkj.client.service.TemplteServiceClient;
import com.hxkj.domain.enums.DirectoryEnum;
import com.hxkj.domain.enums.TemplteExceptionEnum;
import com.hxkj.domain.enums.TemplteTypeEnum;
import com.hxkj.domain.po.*;
import com.hxkj.service.TemplteService;
import com.hxkj.service.article.ChannelService;
import com.hxkj.service.article.ColumnService;
import com.hxkj.service.article.LeafletService;
import com.hxkj.token.utils.TokenUtils;
import com.hxkj.utils.ZipUtils;
import com.integral.mall.file.service.SysFileService;
import com.platform.common.domain.exception.CustomException;
import com.platform.common.domain.exception.CustomMessageException;
import com.platform.common.domain.result.ParameterDataStruct;
import com.platform.common.domain.result.ResultDataStruct;
import com.platform.common.domain.result.ResultMessageStruct;
import com.platform.common.util.StringUtils;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.io.IOUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.OutputStream;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.List;

/**
 * 网站模板实现类
 * <p>
 * Created by yaosy on 2018年6月6日
 */
@Service
@Slf4j
public class TemplteServiceImpl implements TemplteService {


    @Autowired
    private TemplteServiceClient templteServiceClient;

    @Autowired
    private TokenUtils tokenUtils;

    @Autowired
    private LeafletService leafletService;

    @Autowired
    private ColumnService columnService;

    @Autowired
    private ChannelService channelService;


    @Override
    public Templet saveContent(Templet templet) throws Exception {
        try {
            if(templet.getIsDirectory()==1) {
                if (templet.getTempletName() == null) {
                    throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_NAME_BLANK);
                }
                if (StringUtils.isEmpty(templet.getSource())) {
                    throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_CONTENT_BLANK);
                }
            }
            if(templet.getSiteId()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_SITEID);
            }
            if(templet.getParentId()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_PARENT_BLANK);
            }
            // 新增模板文件
            AuthUser auser = (AuthUser) tokenUtils.getTokenUserInfo();
            templet.setCreateor(auser.getUserId());
            templet.setModifyBy(auser.getUserId());
            templet.setCreateTime(System.currentTimeMillis());
            templet.setLastModifiedDate(System.currentTimeMillis());
            templet.setDelTag((byte)0);
            templet.setStatus(templet.getStatus());
            ResultDataStruct result = templteServiceClient.saveContent(templet);
            if(result.getCode()!=200){
                throw new CustomException(TemplteExceptionEnum.getEnumByCode(result.getCode()));
            }
            return (Templet)result.getData();
        }catch (Exception e){
            log.error("新增模板文件失败");
            e.printStackTrace();
            throw e;
        }
    }

    @Override
    public Templet saveFolder(Templet templet) throws Exception {
        try{
            if(templet.getTempletName()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_NAME_BLANK);
            }
            if(templet.getSiteId()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_SITEID);
            }
            if(templet.getParentId()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_PARENT_BLANK);
            }
            AuthUser auser = (AuthUser) tokenUtils.getTokenUserInfo();
            templet.setCreateor(auser.getUserId());
            templet.setModifyBy(auser.getUserId());
            templet.setCreateTime(System.currentTimeMillis());
            templet.setLastModifiedDate(System.currentTimeMillis());
            templet.setDelTag((byte)0);
            templet.setStatus((byte)0);
            templet.setIsDirectory(DirectoryEnum.NO.getCode());
            ResultDataStruct<Templet> result = templteServiceClient.saveFolder(templet);
            if(result.getCode()!=200){
                throw new CustomException(TemplteExceptionEnum.getEnumByCode(result.getCode()));
            }
            return result.getData();
        }catch (Exception e){
            e.printStackTrace();
            log.error("新增模板目录失败");
            throw e;
        }
    }


    @Override
    public List<TemplteTree>  getTempletTree(Templet templet) throws Exception {
        ParameterDataStruct<List<Templet>>  parameterDataStruct = new ParameterDataStruct();
        templet.setSiteId(templet.getSiteId() == null ? 0L : templet.getSiteId());
        try {
            AuthUser auser = (AuthUser) tokenUtils.getTokenUserInfo();
            templet.setCreateor(auser.getUserId());
            templet.setModifyBy(auser.getUserId());
            templet.setCreateTime(System.currentTimeMillis());
            templet.setLastModifiedDate(System.currentTimeMillis());
            templet.setDelTag((byte)0);
            templet.setStatus((byte)0);
            templet.setIsDirectory(DirectoryEnum.NO.getCode());
            ResultDataStruct<List<TemplteTree>>  fun = templteServiceClient.getTempletTree(templet);
            if (fun.getCode() == 200) {
                List<TemplteTree> functionTrees = fun.getData();
                return functionTrees;
            }else {
                throw new CustomException(TemplteExceptionEnum.getEnumByCode(fun.getCode()));
            }
        } catch (Exception e) {
            e.printStackTrace();
            log.error("获取模板功能树失败");
            throw e;
        }
    }

    @Override
    public ResultMessageStruct modify(Templet templet) throws Exception{
        ResultMessageStruct   result = new ResultMessageStruct();
        try{
            if(templet.getSiteId()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_SITEID);
            }
            if(templet.getTempletId()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_ID);
            }
            if(templet.getIsDirectory()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_ISDIRECTORY);
            }
            if(String.valueOf(templet.getIsDirectory()).equals(TemplteTypeEnum.IS_DIRECTORY.getType())){
                if(!templet.getSource().equals(""))
                    templet.setFileName(templet.getSource());
            }
            templet.setLastModifiedDate(System.currentTimeMillis());
            result = templteServiceClient.modify(templet);
            if(result.getCode()!=200){
                throw new CustomException(TemplteExceptionEnum.getEnumByCode(result.getCode()));
            }
        }catch(Exception e){
            e.printStackTrace();
            log.error("修改模板功失败");
            throw e;
        }
        return result;
    }
    @Override
    public ResultMessageStruct remove(Templet templet) throws Exception {
        ResultMessageStruct   result = new ResultMessageStruct();
        if (templet.getTempletId()==0L) {
            throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_ID);
        }
      /*  Article acticle = new Article();
        acticle.setSiteId(templet.getSiteId());
        acticle.setTempletId(templet.getTempletId());
        List<Article> articleList =  articleService.getArticleList(acticle);*/

        //单页
        Leaflet leaflet = new Leaflet();
        leaflet.setSiteId(templet.getSiteId());
        leaflet.setTempletId(templet.getTempletId());
        leaflet.setDelTag(0);
        List<Leaflet>  leafletList = leafletService.getLeafletList(leaflet);
        ResultDataStruct resultDataStructTemplet =  templteServiceClient.get(templet);
        String templetString = JSON.toJSONString(resultDataStructTemplet.getData());
        Templet templet1 = (Templet) JSON.parseObject(templetString, new TypeReference<Templet>(){});
        if(leafletList.size()>0){
            Leaflet leaflet1 =  leafletList.get(0);
            TemplteExceptionEnum.TEMPLTE_EXISTS_NAME_FAILED.setMsg("单页管理:"+leaflet1.getHeadline()+"已经使用了模板"+templet1.getTempletName());
            throw new CustomException(TemplteExceptionEnum.TEMPLTE_EXISTS_NAME_FAILED);
        }

        Column column = new Column();
        column.setSiteId(templet.getSiteId());
        column.setTempletId(templet.getTempletId());
        column.setDelTag((byte)0);
        List<Column>  columnList = columnService.getColumnList(column);
        String columnString = JSON.toJSONString(columnList);
        List<Column> columnList1 = (List<Column>) JSON.parseObject(columnString, new TypeReference<List<Column>>(){});
        if(columnList1.size()>0){
            Column column1 =  columnList1.get(0);
            TemplteExceptionEnum.TEMPLTE_EXISTS_NAME_FAILED.setMsg("文章管理->文章分类:"+column1.getColumnName()+"详情已经使用了模板"+templet1.getTempletName());
            throw new CustomException(TemplteExceptionEnum.TEMPLTE_EXISTS_NAME_FAILED);
        }

        Column column2 = new Column();
        column2.setSiteId(templet.getSiteId());
        column2.setTempId(templet.getTempletId());
        column.setDelTag((byte)0);
        List<Column>  columnListnew = columnService.getColumnList(column);
        String columnString2 = JSON.toJSONString(columnListnew);
        List<Column> columnList2 = (List<Column>) JSON.parseObject(columnString2, new TypeReference<List<Column>>(){});
        if(columnList2.size()>0){
            Column column1 =  columnList.get(0);
            TemplteExceptionEnum.TEMPLTE_EXISTS_NAME_FAILED.setMsg("文章管理->文章分类:"+column2.getColumnName()+"列表已经使用了模板"+templet1.getTempletName());
            throw new CustomException(TemplteExceptionEnum.TEMPLTE_EXISTS_NAME_FAILED);
        }

        Channel channel = new Channel();
        channel.setSiteId(templet.getSiteId());
        channel.setTempletId(templet.getTempletId());
        List<Channel>  channelList = channelService.getChannelList(channel);
        if(channelList!=null && channelList.size()>0){
            Channel channel1 =  channelList.get(0);
            TemplteExceptionEnum.TEMPLTE_EXISTS_NAME_FAILED.setMsg("频道管理:"+channel1.getChannelName()+"列表已经使用了模板"+templet1.getTempletName());
            throw new CustomException(TemplteExceptionEnum.TEMPLTE_EXISTS_NAME_FAILED);
        }

        try{
            templet.setDelTag((byte)1);
            templet.setLastModifiedDate(System.currentTimeMillis());
            AuthUser auser = (AuthUser) tokenUtils.getTokenUserInfo();
            templet.setModifyBy(auser.getUserId());
            result = templteServiceClient.remove(templet);
            if(result.getCode() !=200){
                throw new CustomException(TemplteExceptionEnum.getEnumByCode(result.getCode()));
            }
        }catch(Exception e){
            e.printStackTrace();
            log.error("删除模板功失败");
            throw e;
        }
        return result;
    }

    public ResultDataStruct<Templet> get(Templet templet) throws Exception {
        ResultDataStruct<Templet>  resultDataStruct = new ResultDataStruct();
        try{
            return templteServiceClient.get(templet);
        }catch(Exception e){
            e.printStackTrace();
        }
        return resultDataStruct;
    }

    @Override
    public List<TemplteTree>  getTree(Templet templet) throws Exception {
        ParameterDataStruct<List<Templet>>  parameterDataStruct = new ParameterDataStruct();
        templet.setSiteId(templet.getSiteId() == null ? 0L : templet.getSiteId());
        try {
            ResultDataStruct<List<TemplteTree>>  fun = templteServiceClient.getTree(templet);
            if (fun.getCode() == 200) {
                List<TemplteTree> functionTrees = fun.getData();
                return functionTrees;
            }
        } catch (Exception e) {
            e.printStackTrace();
            log.error("获取模板功能树失败");
            throw e;
        }
        return null;
    }

    @Override
    public Templet saveUploadContent(Templet templet) throws Exception{
        try{
            if(templet.getSiteId()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_SITEID);
            }
            if(templet.getParentId()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_PARENT_BLANK);
            }
            if(templet.getIsDirectory()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_IS_DIRECTORY_FAILED);
            }
            if(templet.getPath()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_PATH_FAILED);
            }
            // 新增模板文件
            AuthUser auser = (AuthUser) tokenUtils.getTokenUserInfo();
            templet.setCreateor(auser.getUserId());
            templet.setModifyBy(auser.getUserId());
            templet.setCreateTime(System.currentTimeMillis());
            templet.setLastModifiedDate(System.currentTimeMillis());
            templet.setDelTag((byte)0);
            templet.setStatus((byte)0);
            templet.setIsDirectory(DirectoryEnum.NO.getCode());

            ResultDataStruct<Templet>  fun = templteServiceClient.saveUploadContent(templet);
            if (fun.getCode() == 200) {
                Templet functionTemplet = fun.getData();
                return functionTemplet;
            }else{
                throw new CustomException(TemplteExceptionEnum.getEnumByCode(fun.getCode()));
            }
        }catch(Exception e){
            log.error("上传文件后保存信息失败!");
            e.printStackTrace();
            throw e;
        }
    }


    @Override
    public void switchTemplte(Templet templet) throws Exception {
        try{
            if(templet.getTempletId()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_ID);
            }
            if(templet.getSiteId()==null){
                throw new CustomException(TemplteExceptionEnum.TEMPLTE_NOT_SITEID);
            }
            AuthUser auser = (AuthUser) tokenUtils.getTokenUserInfo();
            templet.setModifyBy(auser.getUserId());
            templet.setLastModifiedDate(System.currentTimeMillis());
            //获取目录下所有子集
            ResultMessageStruct resultMessageStruct =  templteServiceClient.getAllTempletByTempletId(templet);
            if(resultMessageStruct.getCode() != 200){
                throw new CustomException(TemplteExceptionEnum.getEnumByCode(resultMessageStruct.getCode()));
            }
        }catch(Exception e){
            e.printStackTrace();
            throw e;
        }
    }


    @Autowired
    private SysFileService sysFileService;

    @Value("${cms.templetPath}")
    private String templetPath;

    @Value("${cms.fileRoot}")
    private String fileRoot;

    @Override
    public void downloadTemplet(HttpServletRequest request, HttpServletResponse response, Templet templet) throws Exception{
        FileInputStream fis =null;
        byte[] buffer = new byte[8192];
        int bytesRead = 0;
        OutputStream os = null;
        String path = System.getProperty("java.io.tmpdir")+"/"+templetPath;
        String newpath = System.getProperty("java.io.tmpdir")+"/"+templetPath;
        FileOutputStream outputStream = null;
        try{
            templet.setDelTag((byte)0);
            ResultDataStruct<List<Templet>>   resultDataStruct =  templteServiceClient.getTempletBySiteId(templet);
            if(resultDataStruct.getCode()!=200){
                throw new CustomMessageException(resultDataStruct.getCode(),resultDataStruct.getMessage());
            }

            File file = new File(path);
            if(!file.exists()) file.mkdir();
            List<Templet>  templetList =  resultDataStruct.getData();
            File[] filedata = new File[templetList.size()];
            if(templetList != null && templetList.size() >0){//下载文件以templet来创建文件夹
                int i = 0;
                for(Templet temp : templetList){
                    if(temp.getIsDirectory()==1) {
                        String filename = temp.getFileName();
                        String newPath = System.getProperty("java.io.tmpdir") + "/" + filename.substring(filename.lastIndexOf(templetPath), filename.length())+"/" ;
                        mkDir(new File(newPath));
                        outputStream = new FileOutputStream(newPath+temp.getTempletName());
                        IOUtils.write(temp.getSource(),outputStream);
                        filedata[i++] = new File(newPath + "/" + temp.getTempletName());
                    }
                }
            }
            outputStream.flush();
            path = path +"/tm.zip";
            File zipFile = new File(path);
            ZipUtils.zipFiles(filedata, zipFile);
            response.setContentLength((int) file.length());
            response.setHeader("Content-Disposition", "attachment;filename="
                    + URLEncoder.encode("模板文件.zip", "UTF-8"));// 设置在下载框默认显示的文件名
            response.setContentType("application/octet-stream");

            os = response.getOutputStream();
            fis = new FileInputStream(path);
            while ((bytesRead = fis.read(buffer, 0, 8192)) != -1) {
                os.write(buffer, 0, bytesRead);
            }
            os.flush();
        }catch(Exception e){
            e.printStackTrace();
        }finally {
            try {
                if (fis != null) fis.close();
                if (os != null) os.close();
                if(outputStream !=null) outputStream.close();
                //删除临时目录
                ZipUtils.deletefile(path);//删除zip包
                //删除临时文件
                ZipUtils.deletefile(newpath);
            }catch(Exception e){
                e.printStackTrace();
            }
        }
    }

    @Override
    public List<TemplteTree> visuaTempletTree(Templet templet) throws Exception {
        if (templet.getSiteId() == null){
            throw new CustomMessageException(301,"站点ID为空");
        }
        if (templet.getStatus() == null){
            throw new CustomMessageException(302,"状态不能为空");
        }

        try {
            List<TemplteTree> templteTreeList = new ArrayList<>();
            ResultDataStruct<List<TemplteTree>>  resultDataStruct = templteServiceClient.visuaTempletTree(templet);
            if(resultDataStruct.getData()==null){
                throw new CustomMessageException(303,"没有可用的模板");
            }
            templteTreeList = resultDataStruct.getData();
            return templteTreeList;
        } catch (Exception e) {
            e.printStackTrace();
            throw e;
        }
    }

    /***
     * Java递归创建文件夹
     * **/
    protected void mkDir(File file) {
        if (file.getParentFile().exists()) {
            file.mkdir();
        } else {
            mkDir(file.getParentFile());
            file.mkdir();
        }
    }
}
